<?php

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

    /**
     * Constructor de la clase makinita.
     * @param array $entrada
     * @param array $reglas
     * @return boolean $error
     */

     
class sfTdSchema extends sfTableWidget implements arrayaccess, Iterator, Countable {
    
    private $tds = array();
    private $conditionalClass = '';
    private $conditionalStyle = '';    
    
    
    public  $values = array();
    public  $localRefs = array();
    public  $parentRefs = array();    
    public  $trans = array();    

    
    /**
     * Constructor.
     *
     * Available options:
     *
     *  * id_format:       The format for the generated HTML id attributes (%s by default)
     *  * is_hidden:       true if the form widget must be hidden, false otherwise (false by default)
     *  * default:         The default value to use when rendering the widget
     *  * title:           The title to use when the widget is rendered
     *  * link:            The link of the widget
     *  * conditionalClass:  The conditionalClass for de schema (Tr)
     *                      i.e.
     *                          array('cond1' => 'class1',
     *                                'cond2' => 'class2')
     * 
     * @param array $options     An array of options
     * @param array $attributes  An array of default HTML attributes
     *
     * @see sfWidget
     */
    public function __construct($options = array(), $attributes = array())
    {
      $this->addOption('conditionalClass', null);     
      $this->addOption('conditionalStyle', null);           
      $this->addOption('defaultTdAttributes', array());
      
      parent::__construct($options, $attributes);
      
      $this->tds = array();

    }    
   
    public function offsetSet($offset, $td) {
        if (is_null($offset)) {
            $this->tds[] = $td;
        } else {
            $this->tds[$offset] = $td;
            $td->setName($offset);
        }
        
        $td->setParent($this);

    }
    
    public function offsetExists($offset) {
        return isset($this->tds[$offset]);
    }
    
    public function offsetUnset($offset) {
        unset($this->tds[$offset]);
    }
    
    public function offsetGet($offset) {
        return isset($this->tds[$offset]) ? $this->tds[$offset] : null;
    }
    
    /**
   * Returns the number of form fields (implements the Countable interface).
   *
   * @return integer The number of embedded form fields
   */
    public function count()
    {
      return count($this->tds);
    }    
    
    /**
     * Resets the field names array to the beginning (implements the Iterator interface).
     */
    public function rewind()
    {
      reset($this->tds);
    }

    /**
     * Gets the key associated with the current form field (implements the Iterator interface).
     *
     * @return string The key
     */
    public function key()
    {
      return key($this->tds);
    }

    /**
     * Returns the current form field (implements the Iterator interface).
     *
     * @return mixed The escaped value
     */
    public function current()
    {
      return current($this->tds);
    }

    /**
     * Moves to the next form field (implements the Iterator interface).
     */
    public function next()
    {
      next($this->tds);
    }

    /**
     * Returns true if the current form field is valid (implements the Iterator interface).
     *
     * @return boolean The validity of the current element; true if it is valid
     */
    public function valid()
    {
      return key($this->tds) !== null;
    }
    


    
    /**
     * Sets the conditionalClass for the widget.
     *
     * @param array $conditionalClass The conditionalClass
     *    *
     * @return sfWidget The current widget instance
     */

      public function setConditionalClass($conditionalClass) {
          $this->setOption('conditionalClass', $conditionalClass);     
          return $this;
      }


    /**
     * Sets the setConditionalStyle for the widget.
     *
     * @param array $conditionalStyle The conditionalClass
     *    *
     * @return sfWidget The current widget instance
     */

      public function setConditionalStyle($conditionalStyle) {
          $this->setOption('conditionalStyle', $conditionalStyle);     
          return $this;
      }
      
      
    /**
     * Returns the conditionalClass for the widget.
     *
     * @return string The text
     */

    public function getConditionalClass() {
      return (array)$this->getOption('conditionalClass');
    }
    
    /**
     * Returns the conditionalStyle for the widget.
     *
     * @return string The text
     */

    public function getConditionalStyle() {
      return (array)$this->getOption('conditionalStyle');
    }
    
    
    
    public function preRender(&$dataSource) {

        foreach ($this->tds as $k=>$td)
        {
            if($td->isModelTd())
            {
                $aux = explode('.', (string)$td->getField());
                $this->values[$k] = $this->getElem($dataSource, $aux);
                $this->trans['%'.$k.'%'] = $this->values[$k];
                $this->localRefs['%'.$k.'%'] = '$this->values["'.$k.'"]';            
                $this->parentRefs['%'.$k.'%'] = '$this->parent->values["'.$k.'"]';                            
            }
        }
    }    
    
    
    public function render(&$dataSource) {
        
        
        $this->preRender($dataSource);

        
        $extraClass = '';
        $originalClass = $this->getAttribute('class');
        
        if($this->getConditionalClass() != array())
        {
            foreach($this->getConditionalClass() as $condition => $class)
            {
                $transCondition = 'return ('. strtr($condition, $this->localRefs).');';
                if(eval($transCondition))
                    $extraClass .=' '.strtr($class, $this->trans);                
            }
        }
        
        
        $content = '';
        $this->setAttribute('class', $originalClass.$extraClass);

        
        
        $extraStyle = '';
        $originalStyle = $this->getAttribute('style');
        
        if($this->getConditionalStyle() != array())
        {
            foreach($this->getConditionalStyle() as $condition => $style)
            {
                $transCondition = 'return ('. strtr($condition, $this->localRefs).');';
                if(eval($transCondition))
                    $extraStyle .='; '.strtr($style, $this->trans);                
            }
        }
        
        
        $content = '';
        $this->setAttribute('style', $originalStyle.$extraStyle);
        
        foreach ($this->tds as $td)
        {
            $content .= chr(10).$td->render(); 
        }
        
//        if(($link = $this->getOption('link')) != '')
//            $result = $this->renderContentTag('tr', 
//                            $this->renderContentTag('a',
//                                    $content,array('href'=>strtr($link,$this->trans))), $this->getAttributes());        
//        else
            
       
        $result = $this->renderContentTag('tr', $content, $this->getAttributes());
        
        $this->setAttribute('class', $originalClass);
        $this->setAttribute('style', $originalStyle);
        return $result;
                
    }
    
    
    
    protected function getElem(&$dataSource,$relations) {

        if(count($relations)>1){
            $aux = each($relations);
            unset($relations[$aux['key']]);
            if(isset($dataSource[$aux['value']]))
            {
                return $this->getElem($dataSource[$aux['value']],$relations);
            } else return "*";   //Si la ruta no existe devuelve "*" (para el caso de algun 
                                //ID nulo
            
        }  else {
            $relations = each($relations);
            return $dataSource[$relations['value']];
        }
    }
    
}


?>
